<template>
  <div>
    <!--    三级列表-->
    <Category :disabled="!isListOrAddUpdate"/>
    <!--    三级列表选择完的 数据列表-->
    <el-card v-if="isListOrAddUpdate" style="margin-top: 30px">
      <template #header>
        <el-button type="primary" icon="ele-Plus" @click="addAttrItem" :disabled="!categoryList3Id">添加属性</el-button>
      </template>
      <!--  数据列表    -->
      <el-table border :data="attrInfoList" style="width: 100%">
        <el-table-column align="center" type="index" label="序号" width="60"/>
        <el-table-column align="center" prop="attrName" label="属性名称" width="180"/>
        <el-table-column label="属性名称值">
          <template #default="{row}">
            <el-tag style="margin-right: 15px" class="ml-2" type="danger" v-for="item in row.attrValueList"
                    :key="item.id">
              {{ item.valueName }}
            </el-tag>
          </template>
        </el-table-column>
        <el-table-column align="center" label="操作" width="180">
          <template #default="{row}">
            <el-button @click="fixAttrValue(row)" title="修改" icon="ele-Tickets" type="warning"></el-button>
            <el-popconfirm title="确定删除?" @confirm="removeAttrItem(row.id)">
              <template #reference>
                <el-button title="删除" type="danger" icon="ele-Delete"></el-button>
              </template>
            </el-popconfirm>
          </template>
        </el-table-column>
      </el-table>
    </el-card>
    <!--    添加或者修改显示的组件-->
    <el-card v-else style="margin-top: 30px">
      <!--      属性名-->
      <el-form>
        <el-form-item label="属性名" style="width: 240px">
          <el-input v-model="attrInfoItem.attrName"></el-input>
        </el-form-item>
      </el-form>
      <!--      添加属性值-->
      <div style="margin-top: 20px">
        <el-button type="primary" @click="addAttrValue" :disabled="!attrInfoItem.attrName">添加属性值</el-button>
        <el-button type="default" @click="isListOrAddUpdate=true">取消</el-button>
      </div>

      <!--      属性值数据列表-->
      <el-table border :data="attrInfoItem.attrValueList" style="width: 100%;margin-top: 30px">
        <el-table-column align="center" type="index" label="序号" width="180"/>
        <el-table-column prop="name" label="属性值名称">
          <template #default="{row,$index}">
            <el-input ref="inputEle" @blur="isInput(row,$index)" v-if="row.isEdit" v-model="row.valueName"></el-input>
            <span @click="isSpan(row)" v-else>{{ row.valueName }}</span>
          </template>
        </el-table-column>
        <el-table-column align="center" prop="address" label="操作" width="180">
          <template #default="{row,$index}">
            <el-button type="primary" @click="removeAttrValue($index)">删除</el-button>
          </template>
        </el-table-column>
      </el-table>

      <!--      保存 返回-->
      <div style="margin-top: 20px">
        <el-button type="primary" @click="addOrUpdateAttrItem"
                   :disabled="!attrInfoItem.attrName || attrInfoItem.attrValueList.length === 0">保存
        </el-button>
        <el-button type="default" @click="isListOrAddUpdate=true">返回</el-button>
      </div>
    </el-card>
  </div>
</template>

<script lang="ts">
import {defineComponent} from "vue";

export default defineComponent({
  name: "Attr",
});
</script>

<script setup lang="ts">
import useCategoryStore from "@/stores/category";
import {storeToRefs} from "pinia";
import {nextTick, ref, watch} from "vue";
import {
  type AttrInfoItemType,
  type AttrInfoListType,
  type AttrValueItemType,
  reqAddOrUpdateAttrInfoListAsync, reqDeleteAttrAsync,
  reqGetAttrInfoList
} from "@/api/attr";
import {ElMessage} from "element-plus";
import {cloneDeep} from "lodash";

// 得到categoryStore对象
const categoryStore = useCategoryStore()

// 获取一级列表数据
const {
  categoryList1Id,  // 一级列表数据的查询Id
  categoryList2Id,  // 二级列表数据的查询Id
  categoryList3Id   // 三级列表数据的查询Id
} = storeToRefs(categoryStore)

// 保存 三级列表筛选出来的 属性列表数据
const attrInfoList = ref<AttrInfoListType>([])

// 获取三级列表筛选出来的 属性列表数据
const getAttrInfoList = async () => {
  try {
    const re = await reqGetAttrInfoList(
        categoryList1Id.value as number,
        categoryList2Id.value as number,
        categoryList3Id.value as number
    )
    attrInfoList.value = re
  } catch (e: any) {
    ElMessage.error(e.message)
  }
}

// 挂载时获取 --- > 也就是 当category3Id 有值 三级列表选择完的时候
watch(categoryList3Id, (newVal) => {
  // 当 categoryList3Id 不为 null 的时候 才发请求
  if (!newVal) return
  getAttrInfoList()
})

// 数据列表 和 添加或者删除组件只显示一个  条件渲染
const isListOrAddUpdate = ref(true);  // 默认渲染 数据列表组件

// 保存添加属性的值 和 修改属性的值
const attrInfoItem = ref<AttrInfoItemType>({
  attrName: '',      // 属性名
  categoryId: categoryList3Id.value as number,    // 增修都是三级列表筛选完的值  默认 category3Id 的值
  categoryLevel: 3,  // 等级 3
  attrValueList: []  // 属性值的数组
})

// 收集添加属性的值和属性值的值
const addAttrValue = () => {  // 点击添加属性值调用
  // 收集的属性值
  const addAttrValueItem: AttrValueItemType = {
    valueName: '',
    attrId: undefined,
    isEdit: true   // 功能需要 发请求不需要 为了设置 显示文本框还是输入框  默认输入框
  }
  // 保存到属性值列表中
  attrInfoItem.value.attrValueList.push(addAttrValueItem)

  //  自动让输入框获得焦点
  nextTick(() => {   // DOM渲染是异步的 操作DOM 一定要等 真实DOM渲染完才行
    inputEle.value.focus()
  })
}

// 收集修改属性的值和属性值的值
const fixAttrValue = (row: AttrInfoItemType) => {  // 点击修改属性调用
  // 显示修改组件
  isListOrAddUpdate.value = false

  // 1- 显示需要修改的数据 (数据是对象 需要深拷贝 使用lodash)
  attrInfoItem.value = cloneDeep(row)

  // 2- 设置 显示文本框
  attrInfoItem.value.attrValueList.forEach(item => item.isEdit = false)

}

// 点击添加属性 书写添加功能
const addAttrItem = () => {
  //显示 添加组件的显示
  isListOrAddUpdate.value = false;

  // 清空上一次添加完或者修改完的值
  attrInfoItem.value = {
    attrName: '',      // 属性名
    categoryId: categoryList3Id.value as number,    // 增修都是三级列表筛选完的值  默认 category3Id 的值
    categoryLevel: 3,  // 等级 3
    attrValueList: []  // 属性值的数组
  }
}

// 获取输入框
const inputEle = ref()

// 输入框失焦的时候
const isInput = (row: AttrValueItemType, index: number) => {
  // 显示文本标签
  row.isEdit = false

  // 当添加的时候 属性值为空 剔除
  if (row.valueName === '') attrInfoItem.value.attrValueList.splice(index, 1)

  // 当添加的属性值重复时 剔除
  const isRepetition = attrInfoItem.value.attrValueList.some(item => {
    if (item !== row) {  // 不和自己比较
      return item.valueName === row.valueName
    }
  })
  if (isRepetition) attrInfoItem.value.attrValueList.splice(index, 1)
}
// 点击文本标签显示输入框
const isSpan = (row: AttrValueItemType) => {
  // 显示输入框
  row.isEdit = true;

  // 自动让输入框获得焦点
  nextTick(() => {   // DOM渲染是异步的 操作DOM 一定要等 真实DOM渲染完才行
    inputEle.value.focus()
  })
}

// 添加/修改删除属性值
const removeAttrValue = (index: number) => {
  attrInfoItem.value.attrValueList.splice(index, 1)
}

// 实现添加属性功能和修改属性功能
const addOrUpdateAttrItem = async () => {

  // 删除不必要的数据
  attrInfoItem.value.attrValueList.forEach(item => {
    delete item.isEdit
    return item
  })

  // 判断添加以及修改的时候 属性名不能为空 属性值的数据不能为空
  if (!attrInfoItem.value.attrName || attrInfoItem.value.attrValueList.length === 0) return ElMessage.error(' 属性名不能为空 属性值的数据不能为空')

  // 发送添加/修改的请求
  try {
    if (attrInfoItem.value.id) { // 修改
      await reqAddOrUpdateAttrInfoListAsync(attrInfoItem.value)
      ElMessage.success('修改成功')
    } else {
      await reqAddOrUpdateAttrInfoListAsync(attrInfoItem.value)
      ElMessage.success('添加成功')
    }
  } catch (e: any) {
    ElMessage.error(e.message)
  }

  // 更新数据
  await getAttrInfoList()

  // 显示 列表数据组件
  isListOrAddUpdate.value = true;
}

// 实现删除属性功能
const removeAttrItem = async (id: number) => {
  try {
    await reqDeleteAttrAsync(id)
    ElMessage.success('删除成功')
    // 刷新页面
    await getAttrInfoList()
  } catch (e: any) {
    ElMessage.error(e.message)
  }
}
</script>

<style scoped></style>
